# -*- coding: utf-8 -*-

from odoo import models, fields, api
from datetime import datetime
import json


class OperationLog(models.Model):
    """操作日志模型 - 记录系统所有操作日志"""
    _name = 'device.operation.log'
    _description = '操作日志管理'
    _order = 'operation_time desc, id desc'
    _rec_name = 'display_name'
    
    # 操作人信息
    operator_id = fields.Many2one('device.user', '操作人', required=True)
    operator_name = fields.Char('操作人姓名', related='operator_id.nick_name', store=True)
    operator_username = fields.Char('操作人用户名', related='operator_id.username', store=True)
    
    # 操作信息
    operation_module = fields.Selection([
        ('equipment', '设备管理'),
        ('maintenance', '设备维保'),
        ('training', '设备培训'),
        ('inspection', '设备巡检'),
        ('verification', '设备验证'),
        ('calibration', '设备校准'),
        ('repair', '设备报修'),
        ('department', '部门管理'),
        ('workshop', '车间管理'),
        ('category', '设备类别'),
        ('user', '用户管理'),
        ('role', '角色管理'),
        ('permission', '权限管理'),
        ('announcement', '公告管理'),
        ('system', '系统管理'),
        ('auth', '身份认证'),
        ('file', '文件管理'),
        ('other', '其他')
    ], string='操作模块', required=True)
    
    operation_type = fields.Selection([
        ('create', '新增'),
        ('update', '修改'),
        ('delete', '删除'),
        ('view', '查看'),
        ('export', '导出'),
        ('import', '导入'),
        ('login', '登录'),
        ('logout', '退出'),
        ('upload', '上传'),
        ('download', '下载'),
        ('approve', '审批'),
        ('reject', '拒绝'),
        ('submit', '提交'),
        ('cancel', '取消'),
        ('other', '其他')
    ], string='操作类型', required=True)
    
    operation_content = fields.Text('操作内容', required=True)
    operation_detail = fields.Text('操作详情', help='JSON格式的详细操作信息')
    
    # 时间信息
    operation_time = fields.Datetime('操作时间', required=True, default=fields.Datetime.now)
    
    # 系统信息
    ip_address = fields.Char('IP地址')
    user_agent = fields.Char('用户代理')
    request_method = fields.Char('请求方法')
    request_url = fields.Char('请求URL')
    
    # 关联对象信息
    target_model = fields.Char('目标模型')
    target_id = fields.Integer('目标记录ID')
    target_name = fields.Char('目标记录名称')
    
    # 操作结果
    operation_status = fields.Selection([
        ('success', '成功'),
        ('failed', '失败'),
        ('warning', '警告')
    ], string='操作状态', default='success', required=True)
    
    error_message = fields.Text('错误信息')
    
    # 执行时长（毫秒）
    execution_time = fields.Integer('执行时长(ms)', help='操作执行时长，单位毫秒')
    
    # 部门信息（用于数据权限控制）
    department_id = fields.Many2one('device.department', '操作人部门', related='operator_id.department_id', store=True)
    
    # 显示名称
    display_name = fields.Char('显示名称', compute='_compute_display_name', store=True)
    
    @api.depends('operator_name', 'operation_module', 'operation_type', 'operation_time')
    def _compute_display_name(self):
        for log in self:
            module_dict = dict(log._fields['operation_module'].selection)
            type_dict = dict(log._fields['operation_type'].selection)
            module_name = module_dict.get(log.operation_module, log.operation_module)
            type_name = type_dict.get(log.operation_type, log.operation_type)
            
            time_str = log.operation_time.strftime('%Y-%m-%d %H:%M:%S') if log.operation_time else ''
            log.display_name = f"{log.operator_name or ''} - {module_name} - {type_name} ({time_str})"
    
    @api.model
    def create_log(self, operator_id, module, operation_type, content, **kwargs):
        """创建操作日志的便捷方法"""
        vals = {
            'operator_id': operator_id,
            'operation_module': module,
            'operation_type': operation_type,
            'operation_content': content,
            'operation_time': fields.Datetime.now()
        }
        
        # 可选参数
        optional_fields = [
            'operation_detail', 'ip_address', 'user_agent', 'request_method',
            'request_url', 'target_model', 'target_id', 'target_name',
            'operation_status', 'error_message', 'execution_time'
        ]
        
        for field in optional_fields:
            if field in kwargs:
                vals[field] = kwargs[field]
        
        return self.create(vals)
    
    @api.model
    def log_equipment_operation(self, operator_id, operation_type, equipment_id, content, **kwargs):
        """设备操作日志记录"""
        equipment = self.env['device.equipment'].browse(equipment_id)
        return self.create_log(
            operator_id=operator_id,
            module='equipment',
            operation_type=operation_type,
            content=content,
            target_model='device.equipment',
            target_id=equipment_id,
            target_name=equipment.name if equipment else '',
            **kwargs
        )
    
    @api.model
    def log_user_operation(self, operator_id, operation_type, target_user_id, content, **kwargs):
        """用户操作日志记录"""
        target_user = self.env['device.user'].browse(target_user_id)
        return self.create_log(
            operator_id=operator_id,
            module='user',
            operation_type=operation_type,
            content=content,
            target_model='device.user',
            target_id=target_user_id,
            target_name=target_user.nick_name if target_user else '',
            **kwargs
        )
    
    @api.model
    def log_login(self, user_id, ip_address, user_agent, status='success', error_msg=None):
        """登录日志记录"""
        return self.create_log(
            operator_id=user_id,
            module='auth',
            operation_type='login',
            content='用户登录',
            ip_address=ip_address,
            user_agent=user_agent,
            operation_status=status,
            error_message=error_msg
        )
    
    @api.model
    def log_logout(self, user_id, ip_address):
        """退出日志记录"""
        return self.create_log(
            operator_id=user_id,
            module='auth',
            operation_type='logout',
            content='用户退出',
            ip_address=ip_address
        )
    
    @api.model
    def search_logs(self, filters=None):
        """根据条件搜索日志"""
        domain = []
        
        if not filters:
            filters = {}
        
        # 操作人过滤
        if filters.get('operator_id'):
            domain.append(('operator_id', '=', filters['operator_id']))
        
        if filters.get('operator_name'):
            domain.append(('operator_name', 'ilike', filters['operator_name']))
        
        # 操作模块过滤
        if filters.get('operation_module'):
            domain.append(('operation_module', '=', filters['operation_module']))
        
        # 操作类型过滤
        if filters.get('operation_type'):
            domain.append(('operation_type', '=', filters['operation_type']))
        
        # 操作状态过滤
        if filters.get('operation_status'):
            domain.append(('operation_status', '=', filters['operation_status']))
        
        # 时间范围过滤
        if filters.get('start_time'):
            domain.append(('operation_time', '>=', filters['start_time']))
        
        if filters.get('end_time'):
            domain.append(('operation_time', '<=', filters['end_time']))
        
        # IP地址过滤
        if filters.get('ip_address'):
            domain.append(('ip_address', 'ilike', filters['ip_address']))
        
        # 部门过滤
        if filters.get('department_id'):
            domain.append(('department_id', '=', filters['department_id']))
        
        # 目标对象过滤
        if filters.get('target_model'):
            domain.append(('target_model', '=', filters['target_model']))
        
        if filters.get('target_id'):
            domain.append(('target_id', '=', filters['target_id']))
        
        # 内容关键字过滤
        if filters.get('content_keyword'):
            domain.append(('operation_content', 'ilike', filters['content_keyword']))
        
        return self.search(domain, order='operation_time desc')
    
    @api.model
    def get_statistics(self, filters=None):
        """获取日志统计信息"""
        logs = self.search_logs(filters)
        
        # 按模块统计
        module_stats = {}
        for log in logs:
            module = log.operation_module
            if module not in module_stats:
                module_stats[module] = 0
            module_stats[module] += 1
        
        # 按操作类型统计
        type_stats = {}
        for log in logs:
            op_type = log.operation_type
            if op_type not in type_stats:
                type_stats[op_type] = 0
            type_stats[op_type] += 1
        
        # 按操作状态统计
        status_stats = {}
        for log in logs:
            status = log.operation_status
            if status not in status_stats:
                status_stats[status] = 0
            status_stats[status] += 1
        
        # 按日期统计（最近7天）
        from datetime import timedelta
        daily_stats = {}
        end_date = datetime.now().date()
        for i in range(7):
            date = end_date - timedelta(days=i)
            daily_stats[date.strftime('%Y-%m-%d')] = 0
        
        for log in logs:
            if log.operation_time:
                date_str = log.operation_time.date().strftime('%Y-%m-%d')
                if date_str in daily_stats:
                    daily_stats[date_str] += 1
        
        return {
            'total_count': len(logs),
            'module_stats': module_stats,
            'type_stats': type_stats,
            'status_stats': status_stats,
            'daily_stats': daily_stats
        }
    
    @api.model
    def cleanup_old_logs(self, days=90):
        """清理旧日志（默认保留90天）"""
        from datetime import timedelta
        cutoff_date = datetime.now() - timedelta(days=days)
        old_logs = self.search([('operation_time', '<', cutoff_date)])
        return old_logs.unlink()

